package com.demo.webflux.simple5;

import java.util.concurrent.CompletableFuture;
import java.util.concurrent.CompletionStage;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;

import com.ziroom.common.simple.domain.Student;

import reactivefeign.webclient.WebReactiveFeign;
import reactor.core.publisher.Flux;
import reactor.core.publisher.Mono;

@RestController
public class ProductController {

	private static Logger logger = LoggerFactory.getLogger(ProductController.class);
	private FeignClientService feignService5;
	public ProductController() {
		feignService5 = WebReactiveFeign  //WebClient based reactive feign
				.<FeignClientService>builder()
				.target(FeignClientService.class, "http://127.0.0.1:8085");
	}

    @GetMapping("/slow")
	public Flux<Student> slow() {
		logger.info("/slow");
		// 两次http调用
		Flux<Student> sFlux = feignService5.slow(new Student("xxx", "aaa"), "11", "22", "slow", "bb");
		Flux<Student> sFlux2 = feignService5.slow(new Student("xxx", "bbb"), "11", "22", "slow", "bb");
		// 合并调用结果
		Flux<Student> sFlux3 = Flux.concat(sFlux, sFlux2);
		// 阻塞操作
		CompletionStage<String> completionStage = CompletableFuture.supplyAsync(() -> {
			try {
				Thread.sleep(3000);
			} catch (InterruptedException e) {
				e.printStackTrace();
			}
			logger.info("helloFuture");
			return "helloFuture";
		});
		// 阻塞操作封装成响应式
		Mono<String> str = Mono.fromCompletionStage(completionStage);
		// http的结果和阻塞结果合并
		Flux<Student> sFlux4 = sFlux3.concatMap(t -> str.map(s -> {
			t.setStudentNo(t.getStudentNo() + ", " + s);
			return t;
		}));
		return sFlux4;
	}

	@GetMapping("/fast1")
	public Flux<Student> fast1() throws InterruptedException {
		logger.info("/fast1");
		return feignService5.slow(new Student("xxx", "aaa"), "11", "22", "fast1", "bb");
	}

	@GetMapping("/fast2")
	public Flux<Student> fast2() throws InterruptedException {
		logger.info("/fast2");
		return feignService5.slow(new Student("xxx", "aaa"), "11", "22", "fast2", "bb");
	}

}